#include "EventLoopThread.h"
#include "EventLoop.h"

EventLoopThread::EventLoopThread(const ThreadInitCallback &cb,
                                 const string &name)
: _loop(nullptr)
, _exiting(false)
, _thread(std::bind(&EventLoopThread::threadFunc, this), name)
, _mutex()
, _cond()
, _callback(cb)
{
}
EventLoopThread::~EventLoopThread()
{
    _exiting = true;
    if(_loop != nullptr)
    {
        _loop->quit();
        if(_thread.joinable())
        {
            _thread.join();
        }
    }
}
EventLoop *EventLoopThread::startLoop()
{
    EventLoop *loop = nullptr;
    {
        std::unique_lock lock(_mutex);
        while(_loop == nullptr)
        {
            _cond.wait(lock);
        }
        loop = _loop;
    }
    return loop;
}

void EventLoopThread::threadFunc()
{
    EventLoop loop;
    if(_callback)
    {
        _callback(&loop);
    }

    {
        std::lock_guard lock(_mutex);
        _loop = &loop;
        _cond.notify_one();
    }

    loop.loop();
    std::lock_guard lock(_mutex);
    _loop = nullptr;
}